import React, { useEffect, useState } from 'react'
import { Image, Space, Input, message, Upload, Button, Form } from 'antd'
import { DeleteOutlined, LoadingOutlined, PlusOutlined } from '@ant-design/icons'
import type { FormProps, GetProp, UploadProps } from 'antd'
import type { noticeType } from '@/types'
import type { UploadChangeParam, UploadFile } from 'antd/es/upload/interface'
import http from '@/utils/request'
import { useSearchParams } from 'react-router-dom'
import './edit.scss'

type FileType = Parameters<GetProp<UploadProps, 'beforeUpload'>>[0];

const NoticeRegister:React.FC = () => {
  const[searchParams] = useSearchParams()
  const token = localStorage.getItem('token') || ''
  const [loading, setLoading] = useState(false)
  const [notice, setNotice] = useState<noticeType>({
    cover: '',
    title: '',
    content: []
  })
  const [form] = Form.useForm()

  useEffect(() => {
    http.get(`/notice/detail/${searchParams.get('id')}`).then(res => {
      const resData = res.data
      resData.content = JSON.parse(resData.content)
      setNotice(resData)
      form.setFieldValue('title', resData.title)
    })
  }, [])

  const beforeUpload = (file: FileType) => {
    const isJpgOrPng = file.type === 'image/jpeg' || file.type === 'image/png'
    if (!isJpgOrPng) {
      message.error('只能上传 JPG/PNG 格式!')
    }
    const isLt5M = file.size / 1024 / 1024 < 10
    if (!isLt5M) {
      message.error('图片大小不能超过 10MB!')
    }
    return isJpgOrPng && isLt5M
  }

  const coverChange: UploadProps['onChange'] = (info) => {
    if (info.file.status === 'uploading') {
      setLoading(true)
      return
    }
    if (info.file.status === 'done') {
      setLoading(false)
      const cover = info.file.response.data
      setNotice({
        ...notice,
        cover
      })
    }
  }

  const contentImsChange: (info: UploadChangeParam<UploadFile<any>>, index: number) => void = (info, index) => {
    if (info.file.status === 'uploading') {
      setLoading(true)
      return
    }
    if (info.file.status === 'done') {
      setLoading(false)
      const res = info.file.response
      if(res.code === 0) {
        const url = res.data
        notice.content[index].imgs?.push(url)
        setNotice({
          ...notice
        })
      } else {
        message.error(res.msg || '图片上传失败')
      }
    }
  }

  const deleteItem = (index: number) => {
    notice.content.splice(index, 1)
    setNotice({
      ...notice
    })
  }

  const deleteImg = (index: number, imgIndex: number) => {
    notice.content[index].imgs?.splice(imgIndex, 1)
    setNotice({
      ...notice
    })
  }
  const addContent = (type: 'img' | 'text') => {
    notice.content.push({
      imgs: [],
      text: '',
      type
    })
    setNotice({
      ...notice
    })
  }
  const textChange = (val: any, index: number) => {
    notice.content[index].text = val
    setNotice({
      ...notice
    })
  }

  const back = () => {
    window.history.back()
  }

  const onFinish: FormProps<noticeType>['onFinish'] = (values) => {
    notice.title = values.title
    http.post('/notice/addOrUpdate', {
      ...notice,
      content: JSON.stringify(notice.content)
    }).then(() => {
      message.success('保存成功')
      back()
    })
  }

  const onFinishFailed: FormProps<noticeType>['onFinishFailed'] = (errorInfo) => {
    console.log('Failed:', errorInfo)
  }

  const uploadButton = (
    <button style={{ border: 0, background: 'none' }} type="button">
      {loading ? <LoadingOutlined /> : <PlusOutlined />}
      <div style={{ marginTop: 8 }}>上传图片</div>
    </button>
  )

  const noticeItem = ({ imgs, text, type }: {
    imgs?: string[],
    text?: string,
    type: 'img' | 'text'
  }, index: number) => {
    return (
      <div className="flex-row content-item" key={index}>
        <DeleteOutlined className="delete-item-btn" onClick={() => deleteItem(index)} />
        {
          type === 'img' ?
            <Space size="middle">
              {
                (imgs || []).map((url, imgIndex) => {
                  return <div className="img-container flex-column flex-center" key={`${index}-${imgIndex}`}>
                    <DeleteOutlined className="delete-img-btn" onClick={() => deleteImg(index, imgIndex)} />
                    <Image
                      width={102}
                      src={url}
                    />
                  </div>
                })
              }
              <Upload
                name="file"
                listType="picture-card"
                showUploadList={false}
                action="https://inobelieve.com/hanlin/file/ossUpload"
                data={{ path: 'notice/' }}
                headers={{ token }}
                beforeUpload={beforeUpload}
                onChange={(e) => contentImsChange(e, index)}
              >
                { uploadButton }
              </Upload>
            </Space> :
            <Input.TextArea
              placeholder="请输入正文"
              style={{ maxWidth: 800 }}
              value={text}
              onChange={val => textChange(val.target.value, index)}
              autoSize={{ minRows: 5, maxRows: 10 }}/>
        }
        
      </div>
    )
  }
  return <div className="page-container">
    <Form
      form={form}
      name="basic"
      layout="vertical"
      labelCol={{ span: 8 }}
      wrapperCol={{ span: 24 }}
      style={{ maxWidth: 600 }}
      initialValues={{ remember: true }}
      onFinish={onFinish}
      onFinishFailed={onFinishFailed}
      autoComplete="off"
    >
      <Form.Item<noticeType>
        label="标题"
        name="title"
        initialValue={notice.title}
        rules={[{ required: true, message: '请输入标题!' }]}
      >
        <Input value={notice.title} />
      </Form.Item>
      <Form.Item<noticeType>
        label="封面"
        name="cover"
        validateStatus={notice.cover ? 'success' : 'error'}
        help={notice.cover ? '' : '请上传封面!'}
      >
        <div className="flex-row">
          <Space size="middle">
            {
              notice.cover ? 
                <Image
                  width={102}
                  src={notice.cover}
                /> : null
            }
            <Upload
              name="file"
              listType="picture-card"
              showUploadList={false}
              action="https://inobelieve.com/hanlin/file/ossUpload"
              data={{ path: 'notice/' }}
              headers={{ token }}
              maxCount={1}
              beforeUpload={beforeUpload}
              onChange={coverChange}
            >
              { uploadButton }
            </Upload>
          </Space>
        </div>
      </Form.Item>
      <Form.Item>
        <div className="flex-row">
          <div>公告正文</div>
          <div className="flex1" />
          <Space size="middle">
            <Button onClick={() => addContent('text')} size="small">添加文字</Button>
            <Button onClick={() => addContent('img')} size="small">添加图片</Button>
          </Space>
        </div>
      </Form.Item>
      <Form.Item<noticeType>
        name="content"
        validateStatus={(notice.content[0]?.text || notice.content[0]?.imgs?.length) ? 'success' : 'error'}
        help={(notice.content[0]?.text || notice.content[0]?.imgs?.length) ? '' : '公告正文不能为空!'}
      >
        <div className="note-container">
          {
            notice.content.map((item, index) => {
              return noticeItem(item, index)
            })
          }
        </div>
      </Form.Item>
      <Form.Item>
        <div className="flex-row">
          <div className="flex1" />
          <Space size="middle">
            <Button onClick={back}>取消</Button>
            <Button type="primary" htmlType="submit">
            保存
            </Button>
          </Space>
        </div>
      </Form.Item>
    </Form>
  </div>
}

export default NoticeRegister